package com.demon.net.factory

import com.demon.net.RetrofitFactory
import com.demon.net.converter.CustomGsonConverterFactory
import com.demon.net.factory.IRetrofitFactory.Companion.PREFIX_HTTP
import com.demon.net.factory.IRetrofitFactory.Companion.PREFIX_HTTPS
import com.demon.net.factory.IRetrofitFactory.RetrofitConfig
import okhttp3.OkHttpClient
import okhttp3.logging.HttpLoggingInterceptor
import okhttp3.logging.HttpLoggingInterceptor.Logger
import retrofit2.Retrofit
import retrofit2.converter.gson.GsonConverterFactory
import java.lang.RuntimeException
import java.util.Locale

/**
 * 类简要描述
 * <p/>
 * <p>
 * 类详细描述
 * </p>
 *
 * @author zhaozeyang
 * @date 1/20/21
 */
class CouroutineRetrofitFactory(retrofitConfig: RetrofitConfig) : IRetrofitFactory {

  private val config: RetrofitConfig = retrofitConfig

  override fun <T> createService(clazz: Class<T>): T {
    checkUrl()
    val retrofit = Retrofit.Builder()
        .baseUrl(config.url)
        .addConverterFactory(CustomGsonConverterFactory.create())
        .addConverterFactory(GsonConverterFactory.create())
        .client(createClient())
        .build()
    return retrofit.create(clazz)
  }

  private fun createClient(): OkHttpClient {
    val loggerInterceptor = HttpLoggingInterceptor(object : Logger {
      override fun log(message: String) {
        com.demon.logger.Logger.d(RetrofitFactory.TAG, message)
      }
    })
    loggerInterceptor.level = HttpLoggingInterceptor.Level.BODY
    val httpClientBuilder = OkHttpClient.Builder()
    return httpClientBuilder.apply {
      addInterceptor(loggerInterceptor)
    }.apply {
      config.interceptors?.forEach {
        addInterceptor(it)
      }
    }.apply {
      // TODO 有正式证书需要修改
      if (config.https) {
        // TODO 添加证书
      }
    }.build()
  }

  private fun checkUrl(): Boolean {
    val checkResult = config.url.lowercase(Locale.ROOT).startsWith(PREFIX_HTTP) || config.url.lowercase(Locale.ROOT).startsWith(PREFIX_HTTPS)
    if (!checkResult) {
      throw RuntimeException("url must be start with $PREFIX_HTTP or $PREFIX_HTTPS")
    }
    return checkResult
  }
}